From bc7972dfa7043408c719a8a63645439efe4f71ce Mon Sep 17 00:00:00 2001 From: Benjamin Otte Date: Tue, 7 May 2019 08:56:28 +0200 Subject: [PATCH] csstokenizer: Handle backslash at end of document Testcases included. --- gtk/css/gtkcsstokenizer.c | 42 +++++++++++-------- .../parser/backslash-eof-is-identifier.css | 2 + .../parser/backslash-eof-is-identifier.errors | 2 + .../backslash-eof-is-identifier.ref.css | 3 ++ testsuite/css/parser/backslash.css | 1 + testsuite/css/parser/backslash.errors | 1 + testsuite/css/parser/backslash.ref.css | 0 testsuite/css/parser/meson.build | 6 +++ 8 files changed, 40 insertions(+), 17 deletions(-) create mode 100644 testsuite/css/parser/backslash-eof-is-identifier.css create mode 100644 testsuite/css/parser/backslash-eof-is-identifier.errors create mode 100644 testsuite/css/parser/backslash-eof-is-identifier.ref.css create mode 100644 testsuite/css/parser/backslash.css create mode 100644 testsuite/css/parser/backslash.errors create mode 100644 testsuite/css/parser/backslash.ref.css diff --git a/gtk/css/gtkcsstokenizer.c b/gtk/css/gtkcsstokenizer.c index 90e781c04f..c9a3856657 100644 --- a/gtk/css/gtkcsstokenizer.c +++ b/gtk/css/gtkcsstokenizer.c @@ -633,13 +633,6 @@ is_name (char c) || c == '-'; } -static gboolean -is_valid_escape (char c1, char c2) -{ - return c1 == '\\' - && !is_newline (c2); -} - static gboolean is_non_printable (char c) { @@ -650,6 +643,25 @@ is_non_printable (char c) || c == 0x7F; } +static gboolean +is_valid_escape (const char *data, + const char *end) +{ + switch (end - data) + { + default: + if (is_newline (data[1])) + return FALSE; + G_GNUC_FALLTHROUGH; + + case 1: + return data[0] == '\\'; + + case 0: + return FALSE; + } +} + static inline gsize gtk_css_tokenizer_remaining (GtkCssTokenizer *tokenizer) { @@ -659,15 +671,7 @@ gtk_css_tokenizer_remaining (GtkCssTokenizer *tokenizer) static gboolean gtk_css_tokenizer_has_valid_escape (GtkCssTokenizer *tokenizer) { - switch (gtk_css_tokenizer_remaining (tokenizer)) - { - case 0: - return FALSE; - case 1: - return *tokenizer->data == '\\'; - default: - return is_valid_escape (tokenizer->data[0], tokenizer->data[1]); - } + return is_valid_escape (tokenizer->data, tokenizer->end); } static gboolean @@ -814,7 +818,11 @@ gtk_css_tokenizer_read_escape (GtkCssTokenizer *tokenizer) if (i == 0) { - value = g_utf8_get_char_validated (tokenizer->data, gtk_css_tokenizer_remaining (tokenizer)); + gsize remaining = gtk_css_tokenizer_remaining (tokenizer); + if (remaining == 0) + return 0xFFFD; + + value = g_utf8_get_char_validated (tokenizer->data, remaining); if (value == (gunichar) -1 || value == (gunichar) -2) value = 0; diff --git a/testsuite/css/parser/backslash-eof-is-identifier.css b/testsuite/css/parser/backslash-eof-is-identifier.css new file mode 100644 index 0000000000..feebb23c4d --- /dev/null +++ b/testsuite/css/parser/backslash-eof-is-identifier.css @@ -0,0 +1,2 @@ +a { + animation-name: \ \ No newline at end of file diff --git a/testsuite/css/parser/backslash-eof-is-identifier.errors b/testsuite/css/parser/backslash-eof-is-identifier.errors new file mode 100644 index 0000000000..898da0551f --- /dev/null +++ b/testsuite/css/parser/backslash-eof-is-identifier.errors @@ -0,0 +1,2 @@ +backslash-eof-is-identifier.css:2:3-20: error: GTK_CSS_PARSER_WARNING_SYNTAX +backslash-eof-is-identifier.css:1:3-2:20: error: GTK_CSS_PARSER_WARNING_SYNTAX diff --git a/testsuite/css/parser/backslash-eof-is-identifier.ref.css b/testsuite/css/parser/backslash-eof-is-identifier.ref.css new file mode 100644 index 0000000000..2a9f65267d --- /dev/null +++ b/testsuite/css/parser/backslash-eof-is-identifier.ref.css @@ -0,0 +1,3 @@ +a { + animation-name: �; +} diff --git a/testsuite/css/parser/backslash.css b/testsuite/css/parser/backslash.css new file mode 100644 index 0000000000..b7d5379f9e --- /dev/null +++ b/testsuite/css/parser/backslash.css @@ -0,0 +1 @@ +\ \ No newline at end of file diff --git a/testsuite/css/parser/backslash.errors b/testsuite/css/parser/backslash.errors new file mode 100644 index 0000000000..129660ffca --- /dev/null +++ b/testsuite/css/parser/backslash.errors @@ -0,0 +1 @@ +backslash.css:1:2: error: GTK_CSS_PARSER_ERROR_SYNTAX diff --git a/testsuite/css/parser/backslash.ref.css b/testsuite/css/parser/backslash.ref.css new file mode 100644 index 0000000000..e69de29bb2 diff --git a/testsuite/css/parser/meson.build b/testsuite/css/parser/meson.build index 4ab3fbb305..4aa29a49c3 100644 --- a/testsuite/css/parser/meson.build +++ b/testsuite/css/parser/meson.build @@ -160,6 +160,12 @@ test_data = [ 'background-shorthand-single.ref.css', 'background-size.css', 'background-size.ref.css', + 'backslash.css', + 'backslash.errors', + 'backslash.ref.css', + 'backslash-eof-is-identifier.css', + 'backslash-eof-is-identifier.errors', + 'backslash-eof-is-identifier.ref.css', 'border-color.css', 'border-color-currentcolor.css', 'border-color-currentcolor.ref.css', -- 2.30.2